<template>
  <div id="map-container">
    <div id="map" style="width: 100%; height: 500px;"></div>
    <div class="swipe-control-container">
      <input type="range" id="swipe" value="50" min="0" max="100" />
    </div>
  </div>
</template>

<script lang="ts">
import { defineComponent, onMounted, onUnmounted } from 'vue';
import Map from 'ol/Map';
import View from 'ol/View';
import TileLayer from 'ol/layer/Tile';
import OSM from 'ol/source/OSM';
import ImageTile from 'ol/source/ImageTile';
import { fromLonLat } from 'ol/proj';
import { getRenderPixel } from 'ol/render';
import RenderEvent from 'ol/render/Event';
import { defaults as defaultControls } from 'ol/control';

export default defineComponent({
  name: 'LayerSwipeMap',
  setup() {
    let map: Map | null = null;

    onMounted(() => {
      const gaodeSatelliteLayer = new TileLayer({
        source: new ImageTile({
          url: 'https://webst0{1-4}.is.autonavi.com/appmaptile?style=6&x={x}&y={y}&z={z}',
        }),
        properties: {
          name: '高德卫星图',
        },
      });

      const gaodeRoadLayer = new TileLayer({
        source: new ImageTile({
          url: 'https://webst0{1-4}.is.autonavi.com/appmaptile?x={x}&y={y}&z={z}&lang=zh_cn&size=1&scale=1&style=6',
        }),
        properties: {
          name: '高德路网图',
        },
      });

      const cartoDBPositronLayer = new TileLayer({
        source: new OSM({
          url: 'https://{a-c}.basemaps.cartocdn.com/light_all/{z}/{x}/{y}.png',
        }),
        properties: {
          name: 'CartoDB Positron',
        },
      });

      map = new Map({
        target: 'map',
        layers: [
          cartoDBPositronLayer, // 作为底图
          gaodeSatelliteLayer,   // 作为被卷帘的图层
        ],
        view: new View({
          center: fromLonLat([116.397428, 39.90923]),
          zoom: 10,
        }),
        controls: defaultControls({
          zoom: false,
          rotate: false,
          attribution: false,
        }).extend([]),
      });

      const swipe = document.getElementById('swipe') as HTMLInputElement;

      if (swipe) {
        gaodeSatelliteLayer.on('prerender', function (event) {
          const ctx = (event as RenderEvent).context;
          const mapSize = map!.getSize();
          if (!ctx || !mapSize) {
            return;
          }

          const width = mapSize[0] * (Number(swipe.value) / 100);

          const tl = getRenderPixel(event as RenderEvent, [width, 0]);
          const tr = getRenderPixel(event as RenderEvent, [mapSize[0], 0]);
          const bl = getRenderPixel(event as RenderEvent, [width, mapSize[1]]);
          const br = getRenderPixel(event as RenderEvent, mapSize);

          ctx.save();
          ctx.beginPath();
          ctx.moveTo(tl[0], tl[1]);
          ctx.lineTo(bl[0], bl[1]);
          ctx.lineTo(br[0], br[1]);
          ctx.lineTo(tr[0], tr[1]);
          ctx.closePath();
          ctx.clip();
        });

        gaodeSatelliteLayer.on('postrender', function (event) {
          const ctx = (event as RenderEvent).context;
          if (ctx) {
            ctx.restore();
          }
        });

        swipe.addEventListener('input', function () {
          map!.render();
        });
      }
    });

    onUnmounted(() => {
      if (map) {
        map.setTarget(undefined);
        map = null;
      }
    });

    return {};
  },
});
</script>

<style scoped>
#map-container {
  display: flex;
  flex-direction: column;
  align-items: center; /* 水平居中 */
  width: 100%;
  height: auto; /* 根据内容自适应高度 */
}

#map {
  width: 100%;
  height: 500px;
}

.swipe-control-container {
  width: 100%;
  padding: 10px 0; /* 添加一些上下内边距 */
  display: flex;
  justify-content: center; /* 水平居中滑动条 */
}

#swipe {
  width: 80%; /* 调整滑动条宽度，使其在容器中居中 */
  margin-top: 10px; /* 与地图之间留出一些间距 */
}
</style> 